import { _decorator, Camera, Component, Node } from 'cc';
import { tween, Vec3 } from 'cc';
const { ccclass, property } = _decorator;

@ccclass('CameraManager')
export class CameraManager extends Component {
    public static Instance: CameraManager = null;

    onLoad() {
        CameraManager.Instance = this;
        this.mainCamera = this.getComponent(Camera);
        this.orthoHeight = this.mainCamera.orthoHeight; // 记录初始正交高度
    }

    /** 是否正在抖动 */
    private _isShaking: boolean = false;
    @property({ type: Camera, displayName: '主相机', readonly: true })
    public mainCamera: Camera = null!;

    private orthoHeight: number = 0;   // 初始相机
    private readonly focusHeight: number = 300;   // 聚焦高度

    /**
     * 使用 tween 实现相机抖动效果
     * @param duration 抖动时长（秒）
     * @param strength 抖动强度
     */
    shakeCamera(duration: number = 0.1, strength: number = 10) {
        if (this._isShaking) return; // 已在抖动，直接跳出
        this._isShaking = true;
        const originalPos = this.node.getPosition();
        const shakeTimes = Math.floor(duration * 30); // 约30帧每秒
        const tweens = [];
        for (let i = 0; i < shakeTimes; i++) {
            const offsetX = (Math.random() - 0.5) * strength;
            const offsetY = (Math.random() - 0.5) * strength;
            tweens.push(
                tween(this.node)
                    .to(1 / 30, { position: new Vec3(originalPos.x + offsetX, originalPos.y + offsetY, originalPos.z) })
            );
        }
        // 回到原位置
        tweens.push(
            tween(this.node)
                .to(0.05, { position: originalPos })
                .call(() => {
                    this._isShaking = false;
                })
        );
        // 链式执行所有 tween
        let chain = tweens[0];
        for (let i = 1; i < tweens.length; i++) {
            chain = chain.then(tweens[i]);
        }
        chain.start();
    }


    /**
     * 聚焦到指定位置（如目标点）
     * @param duration 动画时长
     * @param cb 回调
     */
    focusToTarget(duration: number = 0.5, cb: Function = null) {
        let t1 = tween(this.node).to(duration, { position: new Vec3(-250, -20) });
        let t2 = tween(this.mainCamera).to(duration, { orthoHeight: this.focusHeight });
        tween(this.node)
            .parallel(t1, t2)
            .call(() => { cb?.(); })
            .start();
    }

    /**
     * 还原相机到初始状态
     * @param duration 动画时长
     * @param cb 回调
     */
    restoreCamera(duration: number = 0.2, cb: Function = null) {
        let t1 = tween(this.node).to(duration, { position: Vec3.ZERO });
        let t2 = tween(this.mainCamera).to(duration, { orthoHeight: this.orthoHeight });
        tween(this.node)
            .parallel(t1, t2)
            .call(() => { cb?.(); })
            .start();
    }


}


